package com.cqvip.innocence.framework.jwt.service;

import cn.hutool.core.util.StrUtil;
import com.cqvip.innocence.common.constant.JwtConstant;
import com.cqvip.innocence.common.util.html.IpUtils;
import com.cqvip.innocence.common.util.html.ServletUtils;
import com.cqvip.innocence.common.util.jwt.JwtUtils;
import com.cqvip.innocence.common.util.redis.RedisService;
import com.cqvip.innocence.framework.jwt.JwtClaims;
import com.cqvip.innocence.framework.jwt.dto.LoginAdmin;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import javax.servlet.http.HttpServletRequest;
import java.util.concurrent.TimeUnit;

import static com.cqvip.innocence.common.constant.JwtConstant.EXPIRE_TIME;

/**
 * @ClassName AdminTokenService
 * @Description 后台管理员token操作类
 * @Author Innocence
 * @Date 2022/5/9 10:29
 * @Version 1.0
 */
@Component
public class AdminTokenService {

    @Autowired
    private RedisService redisService;

    private String getTokenKey(String userKey) {
        return "admin_token:" + userKey;
    }

    /**
     * 刷新令牌有效期
     *
     * @param loginAdmin 登录信息
     */
    public void refreshToken(LoginAdmin loginAdmin) {
        loginAdmin.setLoginTime(System.currentTimeMillis());
        loginAdmin.setExpireTime(loginAdmin.getLoginTime() + EXPIRE_TIME * 60 * 1000);
        String userKey = getTokenKey(loginAdmin.getUserKey());
        redisService.set(userKey, loginAdmin, EXPIRE_TIME, TimeUnit.MINUTES);
    }

    /**
     * 创建令牌
     * @author Innocence
     * @date 2022/5/9
     * @param loginAdmin 登录用户的基本信息
     * @return java.util.Map<java.lang.String,java.lang.Object>
     */
    public String createAdminToken(LoginAdmin loginAdmin){
        String userKey = loginAdmin.getUserId();
        String userName = loginAdmin.getUserName();
        loginAdmin.setIpAddr(IpUtils.getIpAddr(ServletUtils.getRequest()));
        loginAdmin.setUserKey(userKey);

        refreshToken(loginAdmin);

        JwtClaims jwtClaims = new JwtClaims(userKey, userKey, userName);
        return JwtUtils.createToken(jwtClaims);
    }

    /**
     * 获取当前登录的管理员信息
     * @author Innocence
     * @date 2022/5/9
     * @return com.cqvip.innocence.framework.jwt.dto.LoginAdmin
     */
    public LoginAdmin getLoginAdmin(){
        String token = getTokenFromRequest(ServletUtils.getRequest());
        return getLoginAdmin(token);
    }

    /**
     * 根据令牌获取登录管理员
     * @author Innocence
     * @date 2022/5/9
     * @param token 最终生成的token令牌
     * @return com.cqvip.innocence.framework.jwt.dto.LoginAdmin
     */
    public LoginAdmin getLoginAdmin(String token){
        LoginAdmin loginAdmin;
        if (StrUtil.isNotBlank(token)){
            String userKey = JwtUtils.getUserKey(token);
            Object o = redisService.get(getTokenKey(userKey));
            if (null != o){
                loginAdmin = (LoginAdmin)o;
            }else {
                loginAdmin = null;
            }
        }else {
            loginAdmin = null;
        }
        return loginAdmin;
    }

    /**
     * 从请求头里面获取token
     * @author Innocence
     * @date 2022/4/19
     * @param request
     * @return java.lang.String
     */
    public String getTokenFromRequest(HttpServletRequest request){
        String token = request.getHeader(JwtConstant.AUTHENTICATION);
        if (StrUtil.isNotEmpty(token) && token.startsWith(JwtConstant.PREFIX)) {
            token = token.replaceFirst(JwtConstant.PREFIX, "");
        }
        return token;
    }

    /**
     * 设置登录的管理员账户
     * @author Innocence
     * @date 2022/5/9
     * @param loginAdmin
     * @return void
     */
    public void setLoginAdmin(LoginAdmin loginAdmin){
        if ( null != loginAdmin){
            refreshToken(loginAdmin);
        }
    }

    /**
     * 删除缓存的用户信息
     * @author Innocence
     * @date 2022/5/9
     * @param token 最终生成的token令牌
     * @return void
     */
    public void delLoginAdmin(String token){
        if (StrUtil.isNotBlank(token)){
            String userKey = JwtUtils.getUserKey(token);
            redisService.del(getTokenKey(userKey));
        }
    }
}
